package first.printABC;

import java.util.concurrent.locks.Condition;
import java.util.concurrent.locks.ReentrantLock;

/**
 * @ClassName PrintReentCondi
 * @description:
 * @author: 荣燊
 * @create: 2021-09-09 11:31
 **/
public class PrintReentCondi {
    private static ReentrantLock reentrantLock = new ReentrantLock();
    private static Condition a = reentrantLock.newCondition();
    private static Condition b = reentrantLock.newCondition();
    private static Condition c = reentrantLock.newCondition();
    private static int state = 0;

    private static class PrintA extends Thread {
        @Override
        public void run() {
            reentrantLock.lock();
            try {
                for (int i=0; i<10; i++) {
                    while (state % 3 != 0) {
                        a.await();
                    }
                    System.out.println("A");
                    state++;
                    b.signal();
                }
            } catch (InterruptedException e) {
                e.printStackTrace();
            } finally {
                reentrantLock.unlock();
            }
        }
    }

    private static class PrintB extends Thread {
        @Override
        public void run() {
            reentrantLock.lock();
            try {
                for (int i=0; i<10; i++) {
                    while (state % 3 != 1) {
                        b.await();
                    }
                    System.out.println("B");
                    state++;
                    c.signal();
                }
            } catch (InterruptedException e) {
                e.printStackTrace();
            } finally {
                reentrantLock.unlock();
            }
        }
    }

    private static class PrintC extends Thread {
        @Override
        public void run() {
            reentrantLock.lock();
            try {
                for (int i=0; i<10; i++) {
                    while (state % 3 != 2) {
                        c.await();
                    }
                    System.out.println("C");
                    state++;
                    a.signal();
                }
            } catch (InterruptedException e) {
                e.printStackTrace();
            } finally {
                reentrantLock.unlock();
            }
        }
    }

    public static void main(String[] args) {
        new PrintA().start();
        new PrintB().start();
        new PrintC().start();
    }
}
